package com.huayi.datagovernance.utils;

import com.huayi.datagovernance.common.SysConstant;
import com.huayi.datagovernance.exception.BizException;
import common.parent.system.web.ResponseResult;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang.StringUtils;
import org.springframework.stereotype.Component;
import org.springframework.web.multipart.MultipartFile;
import sun.misc.BASE64Decoder;
import sun.misc.BASE64Encoder;

import javax.servlet.http.HttpServletResponse;
import java.io.*;
import java.util.List;

@Slf4j
@Component
public class FileUtil {

    /**
     * 上传附件接口
     * @param files 文件
     * @param menuName 目录名称
     * @return
     */
    public ResponseResult fileUpload(List<MultipartFile> files, String menuName){
        String filePath ="";
        // 获取文件存储路径
        if(menuName.contains(SysConstant.problemDevice)&&files != null && files.size() > 0) {
            String path = files.get(0).getOriginalFilename();
            String[] pathStr = path.split("_");
            for (int i = 0; i < pathStr.length - 2; i++) {
                menuName = menuName + "/" + pathStr[i];
            }
        }

        filePath=getUploadFilePath(menuName);

        // 上传文件
        if (files != null && files.size() > 0) {
            int i = 0;
            for (MultipartFile file : files) {
                filePath=filePath+file.getOriginalFilename();
                File dest = new File(filePath);
                try {
                    // 文件上传
                    file.transferTo(dest);
                } catch (Exception e) {
                    e.printStackTrace();
                    log.error("上传第" + (i++) + "个文件失败" + e.getMessage());
                }
            }
            return new ResponseResult(true,"上传"+files.size()+"个附件成功！","");
        }
        return new ResponseResult(true,"上传"+files.size()+"个附件成功！","");
    }

    /**
     *  下载文件接口转文件格式
     * @param path
     * @param response
     * @return
     */
    public HttpServletResponse fileDownload2File(String path, HttpServletResponse response) {
        try {
            // path是指欲下载的文件的路径。
            File file = new File(path);
            // 取得文件名。
            String filename = file.getName();
            // 取得文件的后缀名。
            String ext = filename.substring(filename.lastIndexOf(".") + 1).toUpperCase();

            // 以流的形式下载文件。
            InputStream fis = new BufferedInputStream(new FileInputStream(path));
            byte[] buffer = new byte[fis.available()];
            fis.read(buffer);
            fis.close();
            // 清空response
            response.reset();
            // 设置response的Header
            response.addHeader("Content-Disposition", "attachment;filename=" + new String(filename.getBytes()));
            response.addHeader("Content-Length", "" + file.length());
            OutputStream toClient = new BufferedOutputStream(response.getOutputStream());
            response.setContentType("application/octet-stream");
            toClient.write(buffer);
            toClient.flush();
            toClient.close();
        } catch (IOException ex) {
            ex.printStackTrace();
        }
        return response;
    }


    /**
     * 获取文件上传的存放目录
     *
     * @return
     */
    public static String getUploadFilePath(String menuname) {
        StringBuilder filePath = new StringBuilder();
        // 判断操作系统类型，建立文件上传的目录
        String OS = System.getProperty("os.name").toLowerCase();
        // Linux操作系统
        if (OS.indexOf("linux") >= 0) {
            filePath.append("/usr/local/upload/project/");
            // windows操作系统
        } else if (OS.indexOf("windows") >= 0) {
            filePath.append("D:/upload/project/");
        } else {
            throw new BizException("暂不支持除Linux和Windows外的操作系统！");
        }

        if (StringUtils.isNotBlank(menuname)) {
            filePath.append(menuname).append("/");
        }
        File uploadDest = new File(filePath.toString());
        if (!uploadDest.exists()) {
            uploadDest.mkdirs();
            uploadDest.setWritable(true, false);
        }
        return filePath.toString();
    }


    private static String targetFilePath = "C:\\Users\\12299\\Desktop\\1112.jpg";


    public static void main(String[] args) throws Exception {
        String fileStr = getFileStr("C:\\Users\\12299\\Desktop\\20210208160853.jpg");
        System.out.println("fileStr ===" + fileStr);
        System.out.println(generateFile(fileStr, targetFilePath));
        System.out.println("end");
    }

    /**
     * 文件转化成base64字符串
     * 将文件转化为字节数组字符串，并对其进行Base64编码处理
     */
    public static String getFileStr(String filePath) {
        InputStream in = null;
        byte[] data = null;
        // 读取文件字节数组
        try {
            in = new FileInputStream(filePath);
            data = new byte[in.available()];
            in.read(data);
            in.close();
        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            try {
                in.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
        // 对字节数组Base64编码
        BASE64Encoder encoder = new BASE64Encoder();
        // 返回 Base64 编码过的字节数组字符串
        return encoder.encode(data);
    }


    /**
     * base64字符串转化成文件，可以是JPEG、PNG、TXT和AVI等等
     * @param base64FileStr
     * @param filePath
     * @return
     * @throws Exception
     */
    public static boolean generateFile(String base64FileStr, String filePath) throws Exception {
        // 数据为空
        if (base64FileStr == null) {
            System.out.println(" 不行，oops！ ");
            return false;
        }
        BASE64Decoder decoder = new BASE64Decoder();


        // Base64解码,对字节数组字符串进行Base64解码并生成文件
        byte[] byt = decoder.decodeBuffer(base64FileStr);
        for (int i = 0, len = byt.length; i < len; ++i) {
            // 调整异常数据
            if (byt[i] < 0) {
                byt[i] += 256;
            }
        }
        OutputStream out = null;
        InputStream input = new ByteArrayInputStream(byt);
        try {
            // 生成指定格式的文件
            out = new FileOutputStream(filePath);
            byte[] buff = new byte[1024];
            int len = 0;
            while ((len = input.read(buff)) != -1) {
                out.write(buff, 0, len);
            }
        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            out.flush();
            out.close();
        }
        return true;
    }

    /**
     * 读取文件转化成字符串（适用于一切格式，处理中文文件会乱码）
     * 按字节数组读取
     */
    public static String readFileToStrByte(String filePath) {
        InputStream in = null;
        byte[] data = null;
        // 读取文件字节数组
        try {
            in = new FileInputStream(filePath);
            data = new byte[in.available()];
            in.read(data);
        } catch (IOException e) {
            e.printStackTrace();
            return "";
        } finally {
            try {
                if (in != null) {
                    in.close();
                }
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
        // 对字节数组Base64编码
//        BASE64Encoder encoder = new BASE64Encoder();
        // 返回 Base64 编码过的字节数组字符串
//        return encoder.encode(data);
        return new String(data);
    }
}
